#pragma once
#include "..\dxstdafx.h"
#include "..\nodes\Node.h"
#include <string>
#include "..\utils\Logger.h"
#include <map>
#include "Asset.h"
#include "Texture.h"

namespace ds {

class Texture;

class Shader : public Asset {

typedef std::map<std::string,D3DXHANDLE> Handles;

public:
	Shader(const char* handle) : Asset(handle) {}
	Shader(const char* handle,const std::string& fileName,const std::string& technique);
	virtual ~Shader(void);
	virtual void init();	
	ID3DXEffect* getFX();
	void setTechnique();
	bool reload();
	void setColor(const std::string& handle,const Color& c);
	void setFloat(const std::string& handle,float c);
	void setTexture(const std::string& handle,Texture* texture);
	void setVec3(const std::string& handle,const Vec3& v);
	void setActive(const bool active) { 
		m_Active = active; 
	}
	const bool isActive() const { 
		return m_Active; 
	}
protected:
	std::string m_EffectName;
	std::string m_FileName;
	std::string m_Technique;
	ID3DXEffect* m_FX;
	D3DXHANDLE m_hTech;
	Handles m_Handles;
	bool m_Active;
};

class BasicShader : public Shader {

public:
	BasicShader(const char* handle);
	virtual ~BasicShader() {}
	void setTexture(const char* textureName);
	void setDiffuseColor(const Color& color);
	void setAmbientLightColor(const Color& color);
	void setLightColor(const Color& color);
	void setLightDirection(const Vec3& lightDir);
	void setCameraPosition(const Vec3& cameraPos);
};

class ColorShader : public Shader {

public:
	ColorShader(const char* handle,const Color& color);
	void init();	
	void setColor(const Color& color) {
		m_Color = color;
		Shader::setColor("color",m_Color);
	}
	Color getColor() {
		return m_Color;
	}
private:
	Color m_Color;
};

class TransformedTextureShader : public Shader {

public:
	TransformedTextureShader(const char* handle,const std::string& textureName);
	void init();
private:
	std::string m_TextureName;
};

class TransformedTextureColorShader : public Shader {

public:
	TransformedTextureColorShader(const char* handle,const std::string& textureName);
	void init();
private:
	std::string m_TextureName;
};

}

